package zhuyun.code.photoviews.component

import android.view.View
import android.view.ViewGroup
import androidx.recyclerview.widget.RecyclerView

/**
 * @author: Administrator
 * @date: 2021/12/26
 */
class LooperHorizontalLayoutManager:RecyclerView.LayoutManager() {
    override fun generateDefaultLayoutParams(): RecyclerView.LayoutParams {
        return RecyclerView.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT,ViewGroup.LayoutParams.WRAP_CONTENT)
    }

    override fun canScrollHorizontally(): Boolean {
        return true
    }

    override fun onLayoutChildren(recycler: RecyclerView.Recycler?, state: RecyclerView.State?) {
        if(itemCount <= 0){
            return
        }
        if(state!!.isPreLayout){
            return
        }
        detachAndScrapAttachedViews(recycler!!)
        var actualWidth = 0
        for(i in 0 until itemCount){
            val itemView = recycler.getViewForPosition(i)
            addView(itemView)
            measureChildWithMargins(itemView,0,0)
            val width = getDecoratedMeasuredWidth(itemView)
            val height = getDecoratedMeasuredHeight(itemView)
            layoutDecorated(itemView,actualWidth,0,actualWidth+width,height)
            actualWidth += width
            if(actualWidth > getWidth()){
                break
            }
        }
    }

    override fun scrollHorizontallyBy(
        dx: Int,
        recycler: RecyclerView.Recycler?,
        state: RecyclerView.State?
    ): Int {
        val travel = fill(dx,recycler!!,state!!)
        if(travel == 0){
            return 0
        }
        offsetChildrenHorizontal(-travel)
        recyclerHideView(dx,recycler,state)
        return travel
    }

    private fun fill(dx: Int,recycler: RecyclerView.Recycler,state: RecyclerView.State):Int{
        if(dx > 0) {//向左滚动
            val lastView = getChildAt(childCount-1) ?: return 0
            val lastPos = getPosition(lastView)
            if(lastView.right < width){
                var scrap: View
                if(lastPos == itemCount-1){
                    if(looperEnable){
                        scrap =recycler.getViewForPosition(0)
                    } else {
                        return 0
                    }
                } else {
                    scrap = recycler.getViewForPosition(lastPos+1)
                }
                addView(scrap)
                measureChildWithMargins(scrap,0,0)
                val width = getDecoratedMeasuredWidth(scrap)
                val height = getDecoratedMeasuredHeight(scrap)
                layoutDecorated(scrap,lastView.right,0,lastView.right+width,height)
            }
        } else {//向右滚动
            val firstView = getChildAt(0) ?: return 0
            val firstPos = getPosition(firstView)
            if(firstView.left >= 0){
                var scrap:View
                if(firstPos == 0){
                    if(looperEnable){
                        scrap = recycler.getViewForPosition(itemCount-1)
                    } else {
                        return 0
                    }
                } else {
                    scrap = recycler.getViewForPosition(firstPos-1)
                }
                addView(scrap,0)
                measureChildWithMargins(scrap,0,0)
                val width = getDecoratedMeasuredWidth(scrap)
                val height = getDecoratedMeasuredHeight(scrap)
                layoutDecorated(scrap,firstView.left-width,0,firstView.left,height)


            }
        }
        return dx
    }
    private var looperEnable = false
    fun setCanLooperScroll(looperEnable:Boolean){
        this.looperEnable = looperEnable
    }

    private fun recyclerHideView(dx: Int,recycler: RecyclerView.Recycler,state: RecyclerView.State){
        for(i in 0 until childCount){
            val view = getChildAt(i) ?: continue
            if(dx > 0){
                if(view.right < 0){
                    removeAndRecycleView(view,recycler)
                }
            } else {
                if(view.left > width){
                    removeAndRecycleView(view,recycler)
                }
            }
        }
    }
}